package com.cgc.venus.server.user.service;

import com.cgc.venus.server.core.base.AbstractBaseService;
import com.cgc.venus.server.core.bean.response.VenusResponseStatus;
import com.cgc.venus.server.core.exception.VenusException;
import com.cgc.venus.server.core.k8s.inter.K8sNodeService;
import com.cgc.venus.server.core.utils.StringUtil;
import com.cgc.venus.server.user.bean.NodeDataBean;
import com.cgc.venus.server.user.bean.PhysicalGroupBean;
import com.cgc.venus.server.user.inter.InfrastructureService;
import io.fabric8.kubernetes.api.model.Node;
import io.fabric8.kubernetes.api.model.NodeStatus;
import io.fabric8.kubernetes.api.model.Pod;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.EmptyResultDataAccessException;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.stereotype.Service;

import java.sql.ResultSet;
import java.sql.SQLException;
import java.text.DateFormat;
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;


/**
 * Created by xiaobin on 2017/9/8.
 */
@Service
public class InfrastructureImpl extends AbstractBaseService implements InfrastructureService {
    @Autowired
    private JdbcTemplate jdbcTemplate;
    @Autowired
    private K8sNodeService k8sNodeServiceImpl;

    //    物理分区--start
//  根据关键字查询数据库
    @Override
    public List<PhysicalGroupBean> physicalLists(String queryKey) throws VenusException {
        if (queryKey == null) {
            queryKey = "";
        }
        String sql = "select tg.id,tg.name_cn as name_Cn,tg.name_en as name_En,tg.type as radio ,tg.described from t_physical_group  tg where tg.name_cn like ? or tg.described like ?";
        List<Object> objects = new ArrayList<Object>();
        objects.add("%" + queryKey + "%");
        objects.add("%" + queryKey + "%");
        List<PhysicalGroupBean> physicalGroupList = jdbcTemplate.query(sql, new RowMapper<PhysicalGroupBean>() {
            public PhysicalGroupBean mapRow(ResultSet rs, int rowNum) throws SQLException {
                PhysicalGroupBean physicalGroup = new PhysicalGroupBean();
                physicalGroup.setId(rs.getString("id"));
                physicalGroup.setName_Cn(rs.getString("name_Cn"));
                physicalGroup.setName_En(rs.getString("name_En"));
                physicalGroup.setRadio(rs.getInt("radio"));
                physicalGroup.setDescribed(rs.getString("described"));
                return physicalGroup;
            }
        }, objects.toArray());
        return physicalGroupList;
    }
//根据物理分组ID查询物理分组英文名称
    @Override
    public String physicalQueryById(String physicialId)throws VenusException{
        if(StringUtil.isEmpty(physicialId)){
            throw new VenusException(VenusResponseStatus.NO_CONTENT,"异常，物理分组ID为空");
        }
        String sql="select tg.name_en as name_En from t_physical_group tg where tg.id=?";
        List<Object>objects=new ArrayList<Object>();
        objects.add(physicialId);
        Map<String,Object> maps=null;
        try{
            maps=jdbcTemplate.queryForMap(sql, objects.toArray());
        }catch(EmptyResultDataAccessException e){
            throw new VenusException(VenusResponseStatus.NOT_FOUND,"数据库查询异常");
        }
        if(maps.size()==0||maps==null){
            throw new VenusException(VenusResponseStatus.NOT_FOUND,"获取物理分组名称失败");
        };
        String name_En=(String)maps.get("name_En");
        return name_En;
    }

    //数据校验
    @Override
    public boolean validatePhysicalName(String name, String type) throws VenusException {
        if (StringUtil.isEmpty(name)) {
            throw new VenusException(VenusResponseStatus.NO_CONTENT, "物理分组名称不能为空");
        }
        if (StringUtil.isEmpty(type)) {
            throw new VenusException(VenusResponseStatus.NO_CONTENT, "物理分组类型不能为空");
        }
        String sql = "";
        if (type.equals("cn")) {
            sql = "select id from t_physical_group where name_cn='" + name + "'";
        } else if (type.equals("en")) {
            sql = "select id from t_physical_group where name_en='" + name + "'";
        } else {
            return true;
        }
        List r = jdbcTemplate.queryForList(sql);
        if (r != null && r.size() > 0) {
            return true;
        }
        return false;
    }

    // 插入数据库
    @Override
    public boolean physicalSave(PhysicalGroupBean physicalGroup) throws VenusException {
        if (physicalGroup == null) {
            throw new VenusException(VenusResponseStatus.NO_CONTENT, "physicalGroup对象为空");

        }
        if (StringUtil.isEmpty(physicalGroup.getCurrentUserId())) {
            throw new VenusException(VenusResponseStatus.NO_CONTENT, "当前用户信息为空");
        }
        if (StringUtil.isEmpty(physicalGroup.getId())) {
            if (physicalGroup.getName_Cn() == "" || physicalGroup.getName_En() == "" || "null".equals(String.valueOf(physicalGroup.getRadio()))) {
                throw new VenusException(VenusResponseStatus.NO_CONTENT, "提交的中文名称或英文名称，物理分组类型的信息不全，请补全信息");
            }
            List<Object> objects = new ArrayList<Object>();
            objects.add(StringUtil.getUUID());
            objects.add(physicalGroup.getName_Cn());
            objects.add(physicalGroup.getName_En());
            objects.add(physicalGroup.getRadio());
            objects.add(physicalGroup.getDescribed());
            String sql = "insert into t_physical_group(id,name_cn,name_en,type,described,create_time,last_update_time) values(?,?,?,?,?,NOW(),NOW())";
            int row = jdbcTemplate.update(sql, objects.toArray());
            if (row == 0) {
                throw new VenusException(VenusResponseStatus.MYSQL_DB_EXCEPTION, "数据库新增异常");
            }
        }
        return true;
    }

    //    删除物理分区
    @Override
    public boolean physicalDelById(String selectId) throws VenusException {

        String sql = "delete from t_physical_group where id='" + selectId + "'";
        if (StringUtil.isEmpty(selectId)) {
            throw new VenusException(VenusResponseStatus.NO_CONTENT, "没有获取到id信息，请重试");
        }
        int r = jdbcTemplate.update(sql);
        if (r != 1) {
            throw new VenusException(VenusResponseStatus.MYSQL_DB_EXCEPTION, "物理分组删除失败");
        }

        return true;
    }

    //    修改物理分区
    @Override
    public boolean physicalUpdateById(String selectId, int selectRadio, String seletctDescribed) throws VenusException {
        String sql = "update t_physical_group set type='" + selectRadio + "', described='" + seletctDescribed + "' where id='" + selectId + "'";
        if (StringUtil.isEmpty(selectId)) {
            throw new VenusException(VenusResponseStatus.NO_CONTENT, "没有获取到id信息，请重试");
        }
        int[] r = jdbcTemplate.batchUpdate(sql);
        if (r.length == 0 || r == null) {
            throw new VenusException(VenusResponseStatus.MYSQL_DB_EXCEPTION, "物理分组更新失败");
        }

        return true;
    }
//    物理分区end

    //    节点维护start
//    查询物理分组的名称
    @Override
    public List<Map<String, Object>> partitionQuery() throws VenusException {
        String sql = "select id as 'physicalID',name_cn,name_en From t_physical_group ";
        List<Object> objects = new ArrayList<Object>();
        List<Map<String, Object>> maps = new ArrayList<Map<String, Object>>();
        try {
            maps = jdbcTemplate.queryForList(sql);
        } catch (EmptyResultDataAccessException e) {
            throw new VenusException(VenusResponseStatus.NOT_FOUND, "数据库查询异常");

        }
        return maps;
    }

    //    查询K8S的节点运行详细情况
    @Override
    public List<NodeDataBean> nodeDataQuery() throws VenusException {
        List<Node> nodeList = new ArrayList<Node>();
        nodeList = k8sNodeServiceImpl.nodeDataQuery();
        List<NodeDataBean> nodedata = new ArrayList<NodeDataBean>();
        SimpleDateFormat dfs = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date date=new Date();
        DateFormat format=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        String time=format.format(date);
        List<Pod> pods=k8sNodeServiceImpl.getPods();
        for (Node node : nodeList) {
            NodeDataBean dataBean=new NodeDataBean();
            dataBean.setHostName(node.getMetadata().getName());
            NodeStatus status = node.getStatus();
            dataBean.setCPU(status.getCapacity().get("cpu").getAmount());
            int i=Integer.parseInt(status.getCapacity().get("memory").getAmount().replace("Ki",""));
            DecimalFormat df=new DecimalFormat("0.000");
            String temp=df.format((float)i/(1024 * 1024));
            dataBean.setMemory(temp+"Gi");
            //int podnum=k8sNodeServiceImpl.podNumber(dataBean.getHostName());

            int podnum=pods.stream().filter(ts -> node.getMetadata().getName().equals(ts.getStatus().getHostIP())).collect(Collectors.toList()).size();
            String podstring=Integer.toString(podnum);
            dataBean.setPodNumbers(podstring);
            dataBean.setIp(status.getAddresses().get(0).getAddress());

            dataBean.setStatus(status.getConditions().get(4).getStatus());//原来是3,现在修改为4
            dataBean.setPhysicalZone(node.getMetadata().getLabels().get("physical.group"));
            dataBean.setDisk("20G");
            long between = 0;
            try {
                java.util.Date begin = dfs.parse(node.getMetadata().getCreationTimestamp().replace("T"," ").replace("Z",""));
                java.util.Date end = dfs.parse(time);
                between = (end.getTime() - begin.getTime());// 得到两者的毫秒数
            } catch (Exception ex) {
                ex.printStackTrace();
            }
            long day = between / (24 * 60 * 60 * 1000);
            dataBean.setOperationDate(String.valueOf(day)+"天");
            dataBean.setStartTime(node.getMetadata().getCreationTimestamp().replace("T"," ").replace("Z", ""));
            nodedata.add(dataBean);
        }
        if(nodedata.size()==0){
            throw new VenusException(VenusResponseStatus.NO_CONTENT,"获取数据失败");
        }
        return nodedata;
    }
    //    设置节点标签
    @Override
    public boolean nodeLabelSet(String nodeName,Map<String,String> labels) throws VenusException{
        if(StringUtil.isEmpty(nodeName)){
            throw new VenusException(VenusResponseStatus.K8S_EXCEPTION,"nodename信息为空");
        }
        if(labels.isEmpty()){
            throw new VenusException(VenusResponseStatus.K8S_EXCEPTION,"labels信息为空");
        }
        return k8sNodeServiceImpl.nodeLabelSet(nodeName,labels);
    }
// 获取node物理分组的标签
    @Override
    public List<String> nodeLabelQuery() throws VenusException{
        List<String> labeList=k8sNodeServiceImpl.nodeLabel();
        return labeList;
    }

}

